package com.itheima.service.impl;

import com.alibaba.dubbo.config.annotation.Service;
import com.alibaba.fastjson.JSON;
import com.itheima.dao.SetmealDao;
import com.itheima.dao.StatisticsDao;
import com.itheima.pojo.Setmeal;
import com.itheima.pojo.StartAndEnd;
import com.itheima.service.StatisticsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

@Service(interfaceClass = StatisticsService.class)
@Transactional
public class StatisticsServiceImpl implements StatisticsService {
    @Autowired
    private StatisticsDao statisticsDao;
    @Autowired
    private SetmealDao setmealDao;

    //  预约到诊数据统计
    @Override
    public Map<String, Object> findAppointmentCountByTime(Date start, Long monthCount) {
//        创建一个map集合
        Map<String, Object> map = new HashMap<>();
//        创建两个list集合
        List<Integer> listOrderStatus = new LinkedList<>();
        List<Integer> listOrders = new ArrayList<>();
        List<Date> listDate = new ArrayList<>();
//        循环遍历天数，获取明天预约和已到诊人数，并循环添加到集合中
        for (int i = 0; i <= monthCount; i++) {
            Date date = new Date(start.getTime());
            Integer orders = statisticsDao.findAppointmentCountByTime(date);
            Integer orderStatus = statisticsDao.findDiagnosis(date);
            start.setTime(start.getTime() + 1 * (3600 * 1000 * 24));
            listDate.add(date);
            listOrderStatus.add(orderStatus);
            listOrders.add(orders);
        }
//        并添加到map集合中
        map.put("orderStatus", listOrderStatus);
        map.put("orders", listOrders);
        map.put("listDate", listDate);
        return map;
    }

    //    套餐收入统计
    @Override
    public List<Map<String, Object>> packageIncome(StartAndEnd startAndEnd) {
//        把前台传过来的数据用map集合封装起来
        Map<String, Object> startAndEndIntegerMap = new HashMap<>();
        startAndEndIntegerMap.put("start", startAndEnd.getStart());
        startAndEndIntegerMap.put("end", startAndEnd.getEnd());

        List<Map<String, Object>> list = new ArrayList<>();
//        获取到所有套餐的id
        List<Setmeal> all = setmealDao.findAll();
//        定义一个变量获取全部收入
        Map<String, Object> RevenueMap = new HashMap<>();
        Double totalRevenue = 0.0;
//        遍历套餐把套餐id和时间一起传进去
        for (Setmeal setmeal : all) {
//            把套餐传入查询map中
            startAndEndIntegerMap.put("id", setmeal.getId());
            Map<String, Object> map = statisticsDao.packageIncome(startAndEndIntegerMap);
//            获取套餐名字
            map.put("name", setmeal.getName());
//            获取价格
            map.put("value", map.get("value"));
            list.add(map);
            totalRevenue += (Double) map.get("value");
        }
//        获取到总收入，并封装
        RevenueMap.put("name", "总收入");
        RevenueMap.put("value", totalRevenue);
        list.add(RevenueMap);
        return list;
    }

    //    年龄分布统计图
    @Override
    public Map<String, Object> ageDistribution() {
//        把所有的年龄段数据存在List集合中
        List<String> age = new ArrayList<>();
        List<Integer> agelist = new ArrayList<>();
        Map<String, Object> map = new HashMap<>();
//        获得当前时间
        Date presentTime = new Date();
//        获得6年的秒值，减当前时间
        Date startTime = new Date();
        startTime.setYear(startTime.getYear() - 6);
//        创建一个集合，把开始时间和结束是时间都传进去
        Map<String, Date> yearMap = new HashMap<>();
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        Integer numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("0-6岁 婴幼儿");
        agelist.add(numberOfInfants);
//        少儿人数
//        把当前上一次最小年龄当作这一次的最大年龄
        presentTime.setYear(startTime.getYear());
//        把上一次最小年龄在减一部分当作这次的最小年龄
        startTime.setYear(startTime.getYear() - 6);
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("7-12岁 少儿");
        agelist.add(numberOfInfants);
//        青少年
//        把当前上一次最小年龄当作这一次的最大年龄
        presentTime.setYear(startTime.getYear());
//        把上一次最小年龄在减一部分当作这次的最小年龄
        startTime.setYear(startTime.getYear() - 5);
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("13-17岁 青少年");
        agelist.add(numberOfInfants);
//        青年
//        把当前上一次最小年龄当作这一次的最大年龄
        presentTime.setYear(startTime.getYear());
//        把上一次最小年龄在减一部分当作这次的最小年龄
        startTime.setYear(startTime.getYear() - 27);
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("18-45岁 青年");
        agelist.add(numberOfInfants);
        //        中年
//        把当前上一次最小年龄当作这一次的最大年龄
        presentTime.setYear(startTime.getYear());
//        把上一次最小年龄在减一部分当作这次的最小年龄
        startTime.setYear(startTime.getYear() - 23);
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("46-69岁 中年");
        agelist.add(numberOfInfants);
        //        老年
//        把当前上一次最小年龄当作这一次的最大年龄
        presentTime.setYear(startTime.getYear());
//        把上一次最小年龄在减一部分当作这次的最小年龄
        startTime.setYear(startTime.getYear() - 200);
        yearMap.put("start", startTime);
        yearMap.put("end", presentTime);
//        获取对应的年龄段生日信息
        numberOfInfants = statisticsDao.ageDistribution(yearMap);
        age.add("大于69岁 老年");
        agelist.add(numberOfInfants);
        map.put("distribution", agelist);
        map.put("age", age);
        return map;
    }

    //    会员占比统计
    @Override
    public List personnelDistribution() {
//        定义一个集合用来封装数据
        List list = new ArrayList();
        Set<String> set = statisticsDao.getAddress();
        List<Map<String, Object>> people = new ArrayList<>();
        for (String address : set) {
            //        封装地址信息和人员分布
            Map<String, Object> addressMap  = statisticsDao.personnelDistribution(address);
            people.add(addressMap);
        }

//        封装地址和坐标
        List<Map<String, Object>> geoCoordMap = new ArrayList<>();
        for (String address : set) {
//            获取地址信息，传入地址查询坐标地址名称
            String latitude = statisticsDao.getlatitude(address);
//            切割经纬度，获得一个经纬度的地址
            if (latitude != null) {
                String[] split = latitude.split(",");
//            把字符串类型转换成小数类型
                List<Double> doubleList = new ArrayList<>();
                Map<String, Object> map = new HashMap<>();
                for (String s : split) {
                    doubleList.add(Double.valueOf(s));
                }
//            String string = JSON.toJSONString(doubleList);
                map.put(address, doubleList);
//            把读出来的值当作value，查询的值当作name
                geoCoordMap.add(map);
                list.add(people);
                list.add(geoCoordMap);
            }
        }
        return list;
    }
}
